/**
 * 3차원 좌표계를 저장하는 자료 클래스. 평면좌표 x, y 축에 높이(깊이)축 z 추가. 적용 단위 (mm, cm, m, km)
 * 
 * @author sppurple
 * 
 */
public class Point3D {
	private double x, y, z;

	//
	// Method
	//

	/**
	 * Point3D 객체간의 덧셈 연산.
	 * 
	 * @param operand1
	 *            피연산자1
	 * @param operand2
	 *            피연산자2
	 */
	public static Point3D addPoint3D(Point3D operand1, Point3D operand2) {
		Point3D result = new Point3D();
		result.setX(operand1.getX() + operand2.getX());
		result.setY(operand1.getY() + operand2.getY());
		result.setZ(operand1.getZ() + operand2.getZ());
		return result;
	}

	/**
	 * Point3D 객체간의 뺄셈 연산.
	 * 
	 * @param minuend
	 *            피감수
	 * @param subtrahend
	 *            감수
	 */
	public static Point3D subPoint3D(Point3D minuend, Point3D subtrahend) {
		Point3D result = new Point3D();
		result.setX(minuend.getX() - subtrahend.getX());
		result.setY(minuend.getY() - subtrahend.getY());
		result.setZ(minuend.getZ() - subtrahend.getZ());
		return result;
	}

	//
	// Constructor
	//
	Point3D() {
		this.x = 0;
		this.y = 0;
		this.z = 0;
	}

	Point3D(double x, double y, double z) {
		this.x = x;
		this.y = y;
		this.z = z;
	}

	/**
	 * @param x
	 *            x축 좌표(평면좌표)
	 * @param y
	 *            y축 좌표(평면좌표)
	 * @param z
	 *            z축 좌표(높이(깊이)좌표)
	 * @param measure
	 *            단위("mm" : 밀리미터, "cm" : 센티미터, "m" : 미터, "km" : 킬로미터)
	 */
	Point3D(double x, double y, double z, String measure) {
		if (measure == null) {
			this.x = -1;
			this.y = -1;
			this.z = -1;
		} else if (measure == "mm") {
			this.x = x;
			this.y = y;
			this.z = z;
		} else if (measure == "cm") {
			this.x = x * 10;
			this.y = y * 10;
			this.z = z * 10;
		} else if (measure == "m") {
			this.x = x * 1000;
			this.y = y * 1000;
			this.z = z * 1000;
		} else if (measure == "km") {
			this.x = x * 1000000;
			this.y = y * 1000000;
			this.z = z * 1000000;
		} else {
			this.x = -1;
			this.y = -1;
			this.z = -1;
		}
	}

	//
	// Getters and Setters
	//
	public double getX() {
		return x;
	}

	public void setX(double x) {
		this.x = x;
	}

	public double getY() {
		return y;
	}

	public void setY(double y) {
		this.y = y;
	}

	public double getZ() {
		return z;
	}

	public void setZ(double z) {
		this.z = z;
	}

	public double getXPerMillimeter() {
		return x;
	}

	public double getXPerCentimeter() {
		return x / 10;
	}

	public double getXPerMeter() {
		return x / 1000;
	}

	public double getXPerKilometer() {
		return x / 1000000;
	}

	public void setXPerMillimeter(double x) {
		this.x = x;
	}

	public void setXPerCentimeter(double x) {
		this.x = x * 10;
	}

	public void setXPerMeter(double x) {
		this.x = x * 1000;
	}

	public void setXPerKilometer(double x) {
		this.x = x * 1000000;
	}

	public double getYPerMillimeter() {
		return y;
	}

	public double getYPerCentimeter() {
		return y / 10;
	}

	public double getYPerMeter() {
		return y / 1000;
	}

	public double getYPerKilometer() {
		return y / 1000000;
	}

	public void setYPerMillimeter(double y) {
		this.y = y;
	}

	public void setYPerCentimeter(double y) {
		this.y = y * 10;
	}

	public void setYPerMeter(double y) {
		this.y = y * 1000;
	}

	public void setYPerKilometer(double y) {
		this.y = y * 1000000;
	}

	public double getZPerMillimeter() {
		return z;
	}

	public double getZPerCentimeter() {
		return z / 10;
	}

	public double getZPerMeter() {
		return z / 1000;
	}

	public double getZPerKilometer() {
		return z / 1000000;
	}

	public void setZPerMillimeter(double z) {
		this.z = z;
	}

	public void setZPerCentimeter(double z) {
		this.z = z * 10;
	}

	public void setZPerMeter(double z) {
		this.z = z * 1000;
	}

	public void setZPerKilometer(double z) {
		this.z = z * 1000000;
	}
}
